use std::sync::Arc;
use anyhow::Result;

use crate::di::{ServiceContainer, services::*};
use crate::config::{Configs, Server, DataBase, Log, Jwt, Cert};

/// 依赖注入使用示例
/// 
/// 这个模块展示了如何使用依赖注入容器来管理服务的生命周期和依赖关系

/// 创建示例配置
fn create_example_config() -> Configs {
    Configs {
        server: Server {
            name: "example-server".to_string(),
            address: "0.0.0.0:8080".to_string(),
            ssl: false,
        },
        database: DataBase {
            database_url: "mysql://user:password@localhost:3306/example_db".to_string(),
        },
        log: Log {
            filter_level: "info".to_string(),
            with_ansi: true,
            to_stdout: true,
            directory: "./logs".to_string(),
            file_name: "example.log".to_string(),
            rolling: "daily".to_string(),
        },
        jwt: Jwt {
            jwt_secret: "example_secret_key".to_string(),
            jwt_exp: 3600,
        },
        cert: Cert {
            cert: "certs/cert.pem".to_string(),
            key: "certs/key.pem".to_string(),
        },
    }
}

/// 示例：基本的服务注册和解析
pub async fn example_basic_usage() -> Result<()> {
    println!("=== 基本依赖注入使用示例 ===");
    
    // 创建容器
    let container = ServiceContainer::new();
    
    // 注册配置服务
    let config = create_example_config();
    container.register_singleton::<ConfigService, _>(move |_| {
        Ok(ConfigService::new(config.clone()))
    })?;
    
    // 解析配置服务
    let config_service = container.resolve::<ConfigService>()?;
    println!("服务器名称: {}", config_service.config().server.name);
    println!("服务器地址: {}", config_service.config().server.address);
    
    // 验证单例行为
    let config_service2 = container.resolve::<ConfigService>()?;
    let is_same_instance = Arc::ptr_eq(&config_service, &config_service2);
    println!("是否为同一实例: {}", is_same_instance);
    
    Ok(())
}

/// 示例：服务依赖链
pub async fn example_service_dependencies() -> Result<()> {
    println!("\n=== 服务依赖链示例 ===");
    
    let container = ServiceContainer::new();
    
    // 注册配置服务
    let config = create_example_config();
    container.register_singleton::<ConfigService, _>(move |_| {
        Ok(ConfigService::new(config.clone()))
    })?;
    
    // 注册一个示例业务服务，依赖于配置服务
    container.register_singleton::<ExampleBusinessService, _>(|container| {
        let config_service = container.resolve::<ConfigService>()?;
        Ok(ExampleBusinessService::new(config_service))
    })?;
    
    // 注册一个高级服务，依赖于业务服务
    container.register_singleton::<ExampleAdvancedService, _>(|container| {
        let business_service = container.resolve::<ExampleBusinessService>()?;
        let config_service = container.resolve::<ConfigService>()?;
        Ok(ExampleAdvancedService::new(business_service, config_service))
    })?;
    
    // 解析高级服务（会自动解析所有依赖）
    let advanced_service = container.resolve::<ExampleAdvancedService>()?;
    println!("高级服务初始化成功");
    println!("通过依赖链获取的服务器名称: {}", advanced_service.get_server_name());
    
    Ok(())
}

/// 示例：瞬态服务
pub async fn example_transient_services() -> Result<()> {
    println!("\n=== 瞬态服务示例 ===");
    
    let container = ServiceContainer::new();
    
    // 注册瞬态服务
    container.register_transient::<ExampleTransientService, _>(|_| {
        Ok(ExampleTransientService::new())
    })?;
    
    // 解析多次，每次都是新实例
    let service1 = container.resolve::<ExampleTransientService>()?;
    let service2 = container.resolve::<ExampleTransientService>()?;
    let service3 = container.resolve::<ExampleTransientService>()?;
    
    println!("服务1 ID: {}", service1.id());
    println!("服务2 ID: {}", service2.id());
    println!("服务3 ID: {}", service3.id());
    
    let all_different = service1.id() != service2.id() 
        && service2.id() != service3.id() 
        && service1.id() != service3.id();
    println!("所有实例都不同: {}", all_different);
    
    Ok(())
}

/// 示例：多线程环境下的服务使用
pub async fn example_multithreaded_usage() -> Result<()> {
    println!("\n=== 多线程使用示例 ===");
    
    let container = Arc::new(ServiceContainer::new());
    
    // 注册配置服务
    let config = create_example_config();
    container.register_singleton::<ConfigService, _>(move |_| {
        Ok(ConfigService::new(config.clone()))
    })?;
    
    // 创建多个任务并发访问服务
    let mut handles = Vec::new();
    for i in 0..5 {
        let container_clone = Arc::clone(&container);
        let handle = tokio::spawn(async move {
            let config_service = container_clone.resolve::<ConfigService>().unwrap();
            println!("任务 {} 获取到服务器名称: {}", i, config_service.config().server.name);
            
            // 模拟一些工作
            tokio::time::sleep(tokio::time::Duration::from_millis(100)).await;
            
            i
        });
        handles.push(handle);
    }
    
    // 等待所有任务完成
    for handle in handles {
        handle.await?;
    }
    
    println!("所有并发任务完成");
    Ok(())
}

/// 运行所有示例
pub async fn run_all_examples() -> Result<()> {
    example_basic_usage().await?;
    example_service_dependencies().await?;
    example_transient_services().await?;
    example_multithreaded_usage().await?;
    
    println!("\n=== 所有示例运行完成 ===");
    Ok(())
}

// 示例服务定义

/// 示例业务服务
#[derive(Debug)]
pub struct ExampleBusinessService {
    config_service: Arc<ConfigService>,
}

impl ExampleBusinessService {
    pub fn new(config_service: Arc<ConfigService>) -> Self {
        Self { config_service }
    }
    
    pub fn get_database_url(&self) -> &str {
        &self.config_service.config().database.database_url
    }
}

/// 示例高级服务
#[derive(Debug)]
pub struct ExampleAdvancedService {
    business_service: Arc<ExampleBusinessService>,
    config_service: Arc<ConfigService>,
}

impl ExampleAdvancedService {
    pub fn new(
        business_service: Arc<ExampleBusinessService>,
        config_service: Arc<ConfigService>,
    ) -> Self {
        Self {
            business_service,
            config_service,
        }
    }
    
    pub fn get_server_name(&self) -> &str {
        &self.config_service.config().server.name
    }
    
    pub fn get_database_url(&self) -> &str {
        self.business_service.get_database_url()
    }
}

/// 示例瞬态服务
#[derive(Debug)]
pub struct ExampleTransientService {
    id: u64,
}

impl ExampleTransientService {
    pub fn new() -> Self {
        use std::sync::atomic::{AtomicU64, Ordering};
        static COUNTER: AtomicU64 = AtomicU64::new(0);
        
        Self {
            id: COUNTER.fetch_add(1, Ordering::SeqCst),
        }
    }
    
    pub fn id(&self) -> u64 {
        self.id
    }
}

#[cfg(test)]
mod tests {
    use super::*;

    #[tokio::test]
    async fn test_examples() {
        // 运行所有示例作为测试
        run_all_examples().await.unwrap();
    }
}
